package com.linkoog.devtools.intellij.action;

import com.intellij.openapi.actionSystem.AnAction;
import com.intellij.openapi.actionSystem.AnActionEvent;
import com.intellij.openapi.actionSystem.Presentation;
import com.intellij.openapi.actionSystem.ex.CustomComponentAction;
import com.intellij.openapi.project.DumbAware;
import com.intellij.ui.ClickListener;
import com.intellij.ui.SearchTextField;
import org.jetbrains.annotations.NotNull;

import javax.swing.*;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.KeyEvent;
import java.awt.event.MouseEvent;
import java.util.concurrent.atomic.AtomicLong;

public abstract class SearchTextFieldAction extends AnAction implements CustomComponentAction, DumbAware {

    private SearchTextField tableSearchField;
    private final String myDescription;
    private final Icon myIcon;

    public SearchTextFieldAction(String text, String description, Icon icon, int width){
        super(text, description, icon);
        myDescription = description;
        myIcon = icon;

        this.tableSearchField = new SearchTextField(true) {
            private Timer instantSearchTimer;
            private int instantSearchDelay = 350;
            private AtomicLong time =  new AtomicLong(System.currentTimeMillis());

            @Override
            protected boolean preprocessEventForTextField(KeyEvent e) {
                if ((KeyEvent.VK_ENTER == e.getKeyCode()) || ('\n' == e.getKeyChar())) {
                    e.consume();
                    addCurrentTextToHistory();
                    postActionEvent();
                } else {
                    getInstantSearchTimer().restart();
                }
                return super.preprocessEventForTextField(e);
            }

            @Override
            protected void onFocusLost() {
                tableSearchField.addCurrentTextToHistory();
                postActionEvent();
            }

            @Override
            protected void onFieldCleared() {
                postActionEvent();
            }

            public Timer getInstantSearchTimer() {
                if (this.instantSearchTimer == null) {
                    this.instantSearchTimer = new Timer(instantSearchDelay, new ActionListener() {
                        public void actionPerformed(ActionEvent e) {
                            postActionEvent();
                        }
                    });
                    this.instantSearchTimer.setRepeats(false);
                }

                return this.instantSearchTimer;
            }

            public synchronized void postActionEvent() {
                this.getInstantSearchTimer().stop();
                long now = System.currentTimeMillis();
                if (now - time.get() > instantSearchDelay){
                    perform();
                    time.set(now);
                }
            }

            public int getInstantSearchDelay() {
                return this.instantSearchDelay;
            }

            public void setInstantSearchDelay(int instantSearchDelay) {
                this.firePropertyChange("instantSearchDelay", this.instantSearchDelay, this.instantSearchDelay = instantSearchDelay);
            }
        };
        this.tableSearchField.setPreferredSize(new Dimension(width, 30));
    }

    @Override
    public void update(@NotNull final AnActionEvent e) {
        super.update(e);
        Presentation presentation = e.getPresentation();
        presentation.setEnabledAndVisible(true);
        JPanel panel = (JPanel)presentation.getClientProperty(COMPONENT_KEY);
    }

    @Override
    public void actionPerformed(@NotNull AnActionEvent e) {
    }

    public abstract void perform();

    @NotNull
    @Override
    public JComponent createCustomComponent(@NotNull Presentation presentation, @NotNull String place) {
        final JPanel panel = new JPanel(new BorderLayout());
        final JLabel label = new JLabel(myIcon);
        panel.add(label, BorderLayout.EAST);
        panel.add(tableSearchField, BorderLayout.CENTER);
        /*new ClickListener() {
            @Override
            public boolean onClick(@NotNull MouseEvent e, int clickCount) {
                perform();
                return true;
            }
        }.installOn(label);*/
        ClickListener listener = new ClickListener() {
            @Override
            public boolean onClick(@NotNull MouseEvent mouseEvent, int i) {
                return true;
            }
        };

        return tableSearchField;
    }

}
